//
//  DmcWrapper.m
//  MultiScreens
//
//  Created by apple on 14-12-23.
//  Copyright (c) 2014年 skyworth.digital. All rights reserved.
//

#import "DmcWrapper.h"
//#import "SK_MediaDmc.h"
#import "FunctionUtility.h"
//#import "Platinum.h"
#import <Platinum/SK_Platinum.h>


@implementation DmcWrapper{
    NSString *externalUrlPrefix;
}


+(DmcWrapper*)sharedDmsWrapper{
    
    static DmcWrapper *sharedDmcWrapper = nil;
    static dispatch_once_t predicate;
    dispatch_once(&predicate, ^{
        sharedDmcWrapper = [[[self class] alloc] init];
    });
    return sharedDmcWrapper;
}


-(void)startDmc{
    PltMediaControlSetUp();
}

/**
 *  请求DMS上的资源--search方式
 *
 *  @param uuid  dms的uuid
 *  @param type  请求的资源的类型
 *  @param index 页码
 *  @param count 请求的数量
 *
 *  @return 请求结果
 */
-(NSArray*)doSearchWithUuid:(NSString *)uuid Type:(NSString *)type Index:(NSInteger)index Count:(NSInteger)count{
    PLT_SkMediaController *mediaController = getMediaController();
    NPT_Array<PLT_MediaObject> searchResult;
    
    int requestCount = count>0?(int)count:SEARCH_PAGE_SIZE;
   NPT_Result ret = mediaController->DoSearch([uuid cStringUsingEncoding:NSUTF8StringEncoding],[type cStringUsingEncoding:NSUTF8StringEncoding], (int)index, requestCount, &searchResult);
    if (ret != NPT_SUCCESS) {
        return nil;
    }
    NSArray *resultArray =[self parseMediaResult:searchResult];
    return resultArray;
}

-(void)doSearchWithUuid:(NSString *)uuid Type:(NSString *)type Index:(NSInteger)index Count:(NSInteger)count CompleteBlock:(void (^)(NSArray *, int))block{
    NSArray *array = [self doSearchWithUuid:uuid Type:type Index:index Count:count];
    int requestCount = count>0?(int)count:SEARCH_PAGE_SIZE;
    block(array,requestCount);
}


/**
 *   请求DMS上的资源--browse方式
 *
 *  @param uuid          dms的uuid
 *  @param objClassArray 资源类型数组
 *
 *  @return 请求结果
 */
-(NSArray*)doBrowseWithUuid:(NSString*)uuid ObjectClass:(NSArray*)objClassArray{
    PLT_SkMediaController *mediaController = getMediaController();
    NPT_Array<PLT_MediaObject> searchResult;
    NPT_Array<NPT_String> array;
    for (NSString *objClass in objClassArray) {
        array.Add([objClass cStringUsingEncoding:NSUTF8StringEncoding]);
    }
    NPT_Result ret = mediaController->DoBrowse([uuid cStringUsingEncoding:NSUTF8StringEncoding], array, false, &searchResult);
    if (ret != NPT_SUCCESS) {
        return nil;
    }
    NSArray *resultArray =[self parseMediaResult:searchResult];
    return resultArray;
}

/**
 *  请求epg信息
 *
 *  @param uuid      dms的uuid
 *  @param channelID 频道id
 *  @param startDate 开始时间
 *  @param endDate   结束时间
 *
 *  @return 返回结果
 */
-(NSArray*)searchEpgWithUuid:(NSString *)uuid ChannelID:(NSString*)channelID StartDate:(NSDate *)startDate EndDate:(NSDate *)endDate{
    
    NSString *formatStr = @"yyyy-MM-dd";
    NSString *startDateStr = [[FunctionUtility DateToString:startDate WithFormat:formatStr] stringByAppendingString:@"T00:00:00"];
    NSString *endDateStr = [[FunctionUtility DateToString:endDate WithFormat:formatStr] stringByAppendingString:@"T23:59:59"];
    
    NSString *type = [NSString stringWithFormat:@"upnp:class derivedfrom \"object.item.epgItem\"  and upnp:channelID=\"%@\"and upnp:scheduledStartTime>=\"%@\"and upnp:scheduledEndTime<=\"%@\"",channelID,startDateStr,endDateStr];
    
    PLT_SkMediaController *mediaController = getMediaController();
    NPT_Array<PLT_MediaObject> searchResult;
    
    NPT_Result ret = mediaController->DoSearch([uuid cStringUsingEncoding:NSUTF8StringEncoding],[type cStringUsingEncoding:NSUTF8StringEncoding], 0, 0, &searchResult);
    if (ret != NPT_SUCCESS) {
        return nil;
    }
    NSArray *resultArray =[self parseMediaResult:searchResult];
    return resultArray;

}

/**
 *  解析请求结果
 *
 *  @param searchResult 从dms请求到的数据
 *
 *  @return 解析后的数据数组
 */
-(NSArray*)parseMediaResult:(NPT_Array<PLT_MediaObject>)searchResult{
    NSMutableArray *resultArray = [NSMutableArray new];
    
    for (int i =0; i<searchResult.GetItemCount(); i++) {
        PLT_MediaItem* pltMediaItem = (PLT_MediaItem*)searchResult.GetItem(i);
        MediaItem *mediaItem = [[MediaItem alloc] init];
        mediaItem.name = [NSString stringWithCString:pltMediaItem->m_Title encoding:NSUTF8StringEncoding];
        mediaItem.objectClass =[NSString stringWithCString:pltMediaItem->m_ObjectClass.type encoding:NSUTF8StringEncoding];
        if ([mediaItem.objectClass hasPrefix:OBJECT_CLASS_AUDIO_TYPE1]) {
            mediaItem.mediaType = MEDIA_AUDIO;
        }else if ([mediaItem.objectClass hasPrefix:OBJECT_CLASS_IMAGE_TYPE1]){
            mediaItem.mediaType = MEDIA_PHOTOS;
        }else if ([mediaItem.objectClass hasPrefix:OBJECT_CLASS_VIDEO_TYPE1]){
            mediaItem.mediaType = MEDIA_VIDEO;
        }
        mediaItem.title = mediaItem.name;
        mediaItem.date = [NSString stringWithCString:pltMediaItem->m_Date encoding:NSUTF8StringEncoding];
        mediaItem.objectID = [NSString stringWithCString:pltMediaItem->m_ObjectID encoding:NSUTF8StringEncoding];
        mediaItem.descriptionInfo = [NSString stringWithCString:pltMediaItem->m_Description.description encoding:NSUTF8StringEncoding];
        if (pltMediaItem->m_Resources.GetItemCount()>0) {
            PLT_MediaItemResource *firstItem = pltMediaItem->m_Resources.GetFirstItem();
            mediaItem.url = [NSString stringWithCString:firstItem->m_Uri encoding:NSUTF8StringEncoding];
            
            NPT_UInt32 default_int_value = (NPT_UInt32)-1;
            if (firstItem->m_Duration !=default_int_value) {
                NPT_String duration = NPT_String::FromIntegerU(firstItem->m_Duration);
                mediaItem.duration =[NSString stringWithCString:duration encoding:NSUTF8StringEncoding];
            }else{
                NPT_String duration = NPT_String::FromIntegerU(default_int_value);
                mediaItem.duration =[NSString stringWithCString:duration encoding:NSUTF8StringEncoding];
            }
            if (firstItem->m_Size !=default_int_value) {
                NPT_String size = NPT_String::FromIntegerU(firstItem->m_Size);
                mediaItem.size = [NSString stringWithCString:size encoding:NSUTF8StringEncoding];
            }else{
                NPT_String size = NPT_String::FromIntegerU(default_int_value);
                mediaItem.size = [NSString stringWithCString:size encoding:NSUTF8StringEncoding];
                
            }
            
        }
        
        if (pltMediaItem->m_ExtraInfo.album_arts.GetItemCount()>0) {
            PLT_AlbumArtInfo firstItem = *(pltMediaItem->m_ExtraInfo.album_arts.GetFirstItem());
            mediaItem.albumUrl = [NSString stringWithCString:firstItem.uri encoding:NSUTF8StringEncoding];
            
        }else{
            mediaItem.albumUrl = [NSString stringWithCString:pltMediaItem->m_Description.icon_uri encoding:NSUTF8StringEncoding];
        }
        
        if (pltMediaItem->m_People.artists.GetItemCount()>0) {
            NPT_String artist = (*pltMediaItem->m_People.artists.GetFirstItem()).name;
            mediaItem.artist = [NSString stringWithCString:artist encoding:NSUTF8StringEncoding];
        }else{
            mediaItem.artist = @"";
        }
        
        if (!pltMediaItem->m_EpgInfo.channel_ID.IsEmpty()) {
            EpgObjct *epg = [[EpgObjct alloc] init];
  
            epg.channelID = [NSString stringWithCString:pltMediaItem->m_EpgInfo.channel_ID encoding:NSUTF8StringEncoding];
            epg.channelName = [NSString stringWithCString:pltMediaItem->m_EpgInfo.channel_name encoding:NSUTF8StringEncoding];
            epg.scheduledStartTime = [NSString stringWithCString:pltMediaItem->m_EpgInfo.scheduled_startTime encoding:NSUTF8StringEncoding];
            epg.scheduledEndTime = [NSString stringWithCString:pltMediaItem->m_EpgInfo.scheduled_endTime encoding:NSUTF8StringEncoding];
            if (pltMediaItem->m_EpgInfo.is_appointed_play) {
                epg.appointPlay = YES;
                
            }else{
               epg.appointPlay = NO;
            }
            
            if (pltMediaItem->m_EpgInfo.is_appointed_record) {
                epg.appointRecord = YES;
            }else{
                epg.appointRecord = NO;
            }
            mediaItem.epg = epg;
        }

        [resultArray addObject:mediaItem];
    }
    
    return resultArray;

}


/**
 *  设置配对的dmr
 *
 *  @param uuid    dmr的uuid
 *  @param pairNum 配对数
 *
 *  @return 成功返回YES ,
 */
-(BOOL)setPlayingDmrWithUUID:(NSString*)uuid displayPairNum:(int)pairNum{
    
    
    NSLog(@"set----DMR----------------");
    
    NPT_String preRet;
    NSString *result;
    PLT_SkMediaController *mediaController = getMediaController();
    if(nil == uuid)
        return NO;
    if(NULL != mediaController){
        preRet=mediaController->setPlayingRenderer([uuid cStringUsingEncoding:NSUTF8StringEncoding],pairNum);
        result = [NSString stringWithCString:preRet.GetChars() encoding:NSUTF8StringEncoding];
    }
    
    if ([result isEqualToString:@"true"]) {
     //   mediaController->setPlayState([MEDIA_STATE_LOADING cStringUsingEncoding:NSUTF8StringEncoding]);
        
        return YES;
    }
    return NO;
}

/**
 *  设置dmr上播放的媒体资源，以及seekTime
 *
 *  @param item    要播放的媒体资源
 *  @param reltime seekTime
 *
 *  @return 成功返回YES
 */
-(BOOL)setPlayingItem:(MediaItem*)item SeekTime:(NSString *)reltime{
    
    NSLog(@"set avtransporturi = %@",item.url);
    DmcWrapper *sharedDmc = [DmcWrapper sharedDmsWrapper];
    BOOL result= [sharedDmc setAVTransportURI:item.url ItemId:item.objectID Title:item.title ObjectClass:item.objectClass];
    
    dispatch_time_t popTime = dispatch_time(DISPATCH_TIME_NOW, (int64_t)(500 * NSEC_PER_MSEC)); // 1
    dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
    dispatch_after(popTime, queue, ^(void){ //  延时500毫秒 再设置播放，否则出现DMR 不能正常接收url 的bug。
       
        if (reltime) {
            [self setPlaySeek:reltime];
        }
         [sharedDmc setPlayState:MEDIA_STATE_PLAYING];
    });
    
    return result;
}


/**
 *  设置数字电视要播放的频道
 *
 *  @param TVID 频道ID
 */
-(void)setTvPlayByID:(NSInteger)TVID{
    PLT_SkMediaController *mediaController = getMediaController();
    mediaController->setTvPlayById((int)TVID);
}



void changeDidilSpecialCharacters(NPT_String &from,NPT_String &to){
    to = from.Replace("&","&amp;");
    to = to.Replace("<","&lt;");
    to = to.Replace(">","&gt;");
    to = to.Replace("\"","&quot;");
    to = to.Replace("'","&apos;");
}
/**
 *  构造DIDL
 *
 *  @param url
 *  @param id
 *  @param title
 *  @param objectClass
 *
 *  @return
 */
NPT_String creatVirtualDidl(NPT_String url,NPT_String  id,NPT_String title,NPT_String objectClass){
    NPT_String toUrl,toId,toTitle,toObjectClass,didl;
    changeDidilSpecialCharacters(url,toUrl);
    changeDidilSpecialCharacters(id, toId);
    changeDidilSpecialCharacters(title,toTitle);
    changeDidilSpecialCharacters(objectClass,toObjectClass);
    didl="<DIDL-Lite xmlns=\"urn:schemas-upnp-org:metadata-1-0/DIDL-Lite/\" xmlns:dc=\"http://purl.org/dc/elements/1.1/\" xmlns:upnp=\"urn:schemas-upnp-org:metadata-1-0/upnp/\" xmlns:dlna=\"urn:schemas-dlna-org:metadata-1-0/\"><item id=\"" +toId+"\" parentID=\"0\" restricted=\"1\"><dc:title>"+toTitle+"</dc:title><dc:creator>Unknown</dc:creator><upnp:genre>Unknown</upnp:genre><res size=\"800000000\" protocolInfo=\"http-get:*:video/mp4:DLNA.ORG_PN=MPEG4_P2_SP_AAC;DLNA.ORG_OP=01;DLNA.ORG_CI=0;DLNA.ORG_FLAGS=01500000000000000000000000000000\">" +toUrl + "</res><upnp:class>" +toObjectClass+"</upnp:class></item></DIDL-Lite>";
    return didl;
}

/** 设置dmr上播放的媒体资源
 *
 *
 *  @param uri      资源的URL
 *  @param itemid   资源的ID
 *  @param title    资源的名称
 *  @param objClass 资源的类型
 *
 *  @return 成功返回YES
 */

-(BOOL)setAVTransportURI:(NSString *)uri ItemId:(NSString *)itemid Title:(NSString *)title ObjectClass:(NSString *)objClass{
    NPT_String ret="",didl="";
    NSString *result;
    PLT_SkMediaController *mediaController = getMediaController();
    if(NULL != mediaController){
        
        didl = creatVirtualDidl([uri cStringUsingEncoding:NSUTF8StringEncoding],[itemid cStringUsingEncoding:NSUTF8StringEncoding],[title cStringUsingEncoding:NSUTF8StringEncoding], [objClass cStringUsingEncoding:NSUTF8StringEncoding]);

        ret = mediaController->setAVTransportURI([uri cStringUsingEncoding:NSUTF8StringEncoding],didl.GetChars());
    }
    result = [NSString stringWithCString:ret.GetChars() encoding:NSUTF8StringEncoding];

    if ([result isEqualToString:@"true"]) {
        return YES;
    }
    
    
    NSLog(@"SET URL --RESULT---%@",result);
    
    return NO;
}
/**
 *  设置DMR的播放状态
 *
 *  @param state 播放状态
 */
-(void)setPlayState:(NSString *)state{
    if(nil==state){
        return;
    }
    PLT_SkMediaController *mediaController = getMediaController();

    if(NULL != mediaController)
        mediaController->setPlayState([state cStringUsingEncoding:NSUTF8StringEncoding]);
}
/**
 *  设置DMR的播放进度
 *
 *  @param reltime 进度
 */
-(void)setPlaySeek:(NSString*)reltime{
    PLT_SkMediaController *mediaController = getMediaController();
    NPT_String reltimestr=[reltime cStringUsingEncoding:NSUTF8StringEncoding];
    if(NULL != mediaController){
        mediaController->setPlaySeek(reltimestr);
        [self setPlayState:MEDIA_STATE_PLAYING];
    }
}

/**
 *  客户端与盒子进行配对，也就是弹出配对数字
 *
 *  @param uuid       DMR 的uuid
 *  @param deviceName DMR的名称
 *  @param displayNum 要显示的配对数字
 */
-(void)setMediaPair:(NSString *)uuid DeviceName:(NSString *)deviceName DisplayNum:(int)displayNum{
    PLT_SkMediaController *mediaController = getMediaController();
    mediaController->setMediaPair([uuid cStringUsingEncoding:NSUTF8StringEncoding], [deviceName cStringUsingEncoding:NSUTF8StringEncoding], displayNum, true);
}
/**
 *  取消弹出的配对数字
 *
 *  @param uuid       DMR的uuid
 *  @param deviceName DMR的名称
 *  @param displayNum 显示的配对数字
 */
-(void)cancelSetMediaPair:(NSString *)uuid DeviceName:(NSString *)deviceName DisplayNum:(int)displayNum{
    PLT_SkMediaController *mediaController = getMediaController();
    mediaController->setMediaPair([uuid cStringUsingEncoding:NSUTF8StringEncoding], [deviceName cStringUsingEncoding:NSUTF8StringEncoding], displayNum, false);
}
/**
 *  设置DMR的音量
 *
 *  @param volume 音量
 */
-(void)setVolume:(NSInteger)volume{
    
    PLT_SkMediaController *mediaController = getMediaController();
    mediaController->setMediaVolume((int)volume);
}

/**
 *  获取DMR的音量，返回在dmcActionCallAPPIOS回调中
 */
-(void)tryGetVolume{
    PLT_SkMediaController *mediaController = getMediaController();
    mediaController->tryGetVolume();
}


#pragma mark CallBack
/**
 *  dmc的回调，包含dms,dmr等一些状态变化信息
 *
 *  @param actionName
 *  @param NPT_Map<NPT_String
 *  @param value
 */
void dmcActionCallAPPIOS(NPT_String& actionName,NPT_Map<NPT_String, NPT_String>& value){
    
    NSLog(@"fun %s  ",__FUNCTION__);
    
    if (strcmp(actionName, "OnMSAdded")==0) {
        
        NPT_String *frindlyName;
        value.Get("FriendlyName", frindlyName);
        
      NSString *nsFriendlyName =  [NSString stringWithCString:*frindlyName encoding:NSUTF8StringEncoding];
        frindlyName = NULL;
    
        NPT_String *uuid;
        value.Get("Uuid", uuid);
        
        NSString *nsUuid = [NSString stringWithCString:*uuid encoding:NSUTF8StringEncoding];
        uuid = NULL;
        NPT_String *type;
        value.Get("Type", type);
        NSString *nsType = [NSString stringWithCString:*type encoding:NSUTF8StringEncoding];
        type = NULL;
        NPT_String *descriptionUrl;
        value.Get("DescriptionUrl", descriptionUrl);
        NSString *nsDescriptionUrl = [NSString stringWithCString:*descriptionUrl encoding:NSUTF8StringEncoding];
        descriptionUrl = NULL;
        DlnaDevice *device = [[DlnaDevice alloc] initWithUuid:nsUuid FriendlyName:nsFriendlyName Type:nsType DescriptionUrl:nsDescriptionUrl];
        if ([[DmcWrapper sharedDmsWrapper].delegate respondsToSelector:@selector(OnMSAdded:)]) {
                [[DmcWrapper sharedDmsWrapper].delegate OnMSAdded:device];
        }
    
        
    }else if (strcmp(actionName, "OnMSRemoved")==0){
        
        NPT_String *uuid;
        value.Get("Uuid", uuid);
        
        NSString *nsUuid = [NSString stringWithCString:*uuid encoding:NSUTF8StringEncoding];
        uuid = NULL;
        DlnaDevice *device = [[DlnaDevice alloc] initWithUuid:nsUuid FriendlyName:nil Type:nil DescriptionUrl:nil];
        
      
        if ([[DmcWrapper sharedDmsWrapper].delegate respondsToSelector:@selector(OnMSRemoved:)]) {
            [[DmcWrapper sharedDmsWrapper].delegate OnMSRemoved:device];
        }
        

    }else if (strcmp(actionName, "OnMRAdded")==0){
        
        NPT_String *frindlyName;
        value.Get("FriendlyName", frindlyName);
        
        NSString *nsFriendlyName =  [NSString stringWithCString:*frindlyName encoding:NSUTF8StringEncoding];
        frindlyName = NULL;

        NPT_String *uuid;
        value.Get("Uuid", uuid);
        
        NSString *nsUuid = [NSString stringWithCString:*uuid encoding:NSUTF8StringEncoding];
        uuid = NULL;
        NPT_String *type;
        value.Get("Type", type);
        NSString *nsType = [NSString stringWithCString:*type encoding:NSUTF8StringEncoding];
        type = NULL;
        NPT_String *descriptionUrl;
        value.Get("DescriptionUrl", descriptionUrl);
        NSString *nsDescriptionUrl = [NSString stringWithCString:*descriptionUrl encoding:NSUTF8StringEncoding];
        descriptionUrl = NULL;
        DlnaDevice *device = [[DlnaDevice alloc] initWithUuid:nsUuid FriendlyName:nsFriendlyName Type:nsType DescriptionUrl:nsDescriptionUrl];
        if ([[DmcWrapper sharedDmsWrapper].delegate respondsToSelector:@selector(OnMRAdded:)]) {
            [[DmcWrapper sharedDmsWrapper].delegate OnMRAdded:device];
        }


    }else if (strcmp(actionName, "OnMRRemoved")==0){
        
        NPT_String *uuid;
        value.Get("Uuid", uuid);
        
        NSString *nsUuid = [NSString stringWithCString:*uuid encoding:NSUTF8StringEncoding];
        uuid = NULL;
        DlnaDevice *device = [[DlnaDevice alloc] initWithUuid:nsUuid FriendlyName:nil Type:nil DescriptionUrl:nil];
        if ([[DmcWrapper sharedDmsWrapper].delegate respondsToSelector:@selector(OnMRRemoved:)]) {
            [[DmcWrapper sharedDmsWrapper].delegate OnMRRemoved:device];
        }
        
    }else if (strcmp(actionName, "OnMRStateVariablesChanged")==0){
      
        if (value.HasKey("TransportState")==true) {
            NPT_String *cString;
            value.Get("TransportState", cString);
            NSString *transportState = [NSString stringWithCString:*cString encoding:NSUTF8StringEncoding];
            cString =NULL;
          //  NSLog(@"transportState--%@",transportState);
           // [[DmcWrapper sharedDmsWrapper].delegate OnMRPlayStateChanged:transportState];
            [[NSNotificationCenter defaultCenter] postNotificationName:NOTIFICATION_ONMRPLAYSTATECHANGED object:transportState];
            
        }else if (value.HasKey("CurrentMediaDuration")==true){
            NPT_String *cString;
            value.Get("CurrentMediaDuration", cString);
           // NSString *currentMediaDuration = [NSString stringWithCString:*cString encoding:NSUTF8StringEncoding];
            
        }else if (value.HasKey("AbsoluteTimePosition")==true){
            NPT_String *cString;
            value.Get("AbsoluteTimePosition", cString);
            NSString *absoluteTimePosition = [NSString stringWithCString:*cString encoding:NSUTF8StringEncoding];
            cString =NULL;
           // [[DmcWrapper sharedDmsWrapper].delegate OnMRPlayAbsoluteTime:absoluteTimePosition];
            [[NSNotificationCenter defaultCenter] postNotificationName:NOTIFICATION_ONPLAYABSOLUTETIME object:absoluteTimePosition];
          //  NSLog(@"absoluteTimePosition==%@",absoluteTimePosition);
        }else if (value.HasKey("Volume")==true){
            NPT_String *cString;
            value.Get("Volume", cString);
            NSString *volume = [NSString stringWithCString:*cString encoding:NSUTF8StringEncoding];
            cString =NULL;
            NSLog(@"Volume--%@",volume);
        }else if (value.HasKey("Mute")==true){
            NPT_String *cString;
            value.Get("Mute", cString);
//            NSString *mute = [NSString stringWithCString:*cString encoding:NSUTF8StringEncoding];
            
//            NSLog(@"Mute--%@",mute);
        }
    
    }
    return ;
}


@end
